package com.tang.h2_demo.global.log;

import com.alibaba.fastjson.JSON;
import com.tang.h2_demo.domain.OperatorLog;
import com.tang.h2_demo.global.ResultBuilder;
import com.tang.h2_demo.service.OperatorLogService;
import lombok.extern.slf4j.Slf4j;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Pointcut;
import org.aspectj.lang.reflect.MethodSignature;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import org.springframework.util.StringUtils;

import java.lang.reflect.Method;


@Slf4j
@Aspect
@Component
public class LogWriteAspect {


    @Autowired
    private OperatorLogService operatorLogService;


    @Pointcut("execution(* com.tang..*.controller..*.*(..))")
    public void Pointcut() {
    }

    /**
     * @param point
     * @throws Exception
     */
    @Around("Pointcut()")
    public Object beforeMethod(ProceedingJoinPoint point) throws Throwable {
        MethodSignature signature = (MethodSignature) point.getSignature();
        Method method = signature.getMethod();
        /**
         * 参数
         */
        Object[] args = point.getArgs();

        try {
            Object result = point.proceed();

            /**
             * todo 正常日志记录成功 异步调用保存
             */
            operatorLogService.save(createdOperatorLog("zhangsan", method.getDeclaringClass().getSimpleName() + "." + method.getName(), "1", args, result));
            return result;
        } catch (Throwable throwable) {
            /**
             *   todo 异常日志记录 异步调用保存
             */
            operatorLogService.save(createdOperatorLog("zhangsan", method.getName(), "0", args, throwable.getMessage()));
            throwable.printStackTrace();
            throw throwable;
        }
    }

    /**
     * @param operator
     * @param methodName
     * @param status
     * @param args
     * @param result
     * @return
     */
    private OperatorLog createdOperatorLog(String operator,
                                           String methodName,
                                           String status,
                                           Object[] args,
                                           Object result) {
        OperatorLog operatorLog = new OperatorLog();
        operatorLog.setOperator(operator);
        operatorLog.setMethodName(methodName);
        operatorLog.setStatus(status);
        String paramStr = JSON.toJSONString(args);
        if (StringUtils.hasLength(paramStr) && paramStr.length() > 100) {
            operatorLog.setParamter(paramStr.substring(0, 100));
        } else {
            operatorLog.setParamter(paramStr);
        }
        String resultStr = JSON.toJSONString(result);
        if (StringUtils.hasLength(resultStr) && resultStr.length() > 100) {
            operatorLog.setParamter(resultStr.substring(0, 100));
        } else {
            operatorLog.setResult(resultStr);
        }
        return operatorLog;
    }
}